package hawk.example.bookstore.repository;

import glz.hawkframework.sql.condition.Condition;
import glz.hawkframework.sql.util.QueryWrapper;

import hawk.example.bookstore.po.BookPo;
import hawk.example.bookstore.update.BookColumnUpdate;
import hawk.example.bookstore.update.BookUpdate;

import java.math.BigInteger;
import java.util.List;
import java.util.Optional;
import java.util.function.Supplier;
import javax.annotation.Nullable;

public interface BookRepository {
    void insert(BookPo bookPo);

    void insertSelective(BookPo bookPo);

    void insertMultiple(List<BookPo> bookPos, int chunkSize);

    void insertMultiple(List<BookPo> bookPos);

    void deleteByPrimaryKey(BigInteger bookId, Long recordVersion);

    void updateByPrimaryKey(BookUpdate bookUpdate, BigInteger bookId, Long recordVersion);

    Optional<BookPo> getByPrimaryKey(BigInteger bookId);

    /**
     * Throws an exception if found no required record by the primary key.
     */
    BookPo loadByPrimaryKey(BigInteger bookId);

    /**
     * Throws the supplied exception if found no required record by the primary key.
     */
    <E extends Throwable> BookPo loadByPrimaryKey(BigInteger bookId, Supplier<? extends E> exceptionSupplier) throws E;

    boolean existByPrimaryKey(BigInteger bookId);

    /**
     * Throws an exception if the required record doesn't exist
     */
    void assertExistByPrimaryKey(BigInteger bookId);

    /**
     * Throws the supplied exception if the required record doesn't exist
     */
    <E extends Throwable> void assertExistByPrimaryKey(BigInteger bookId, Supplier<? extends E> exceptionSupplier) throws E;

    Optional<BookPo> queryOne(QueryWrapper queryWrapper);

    List<BookPo> queryMany(QueryWrapper queryWrapper);

    /**
     * Throws an exception if found no required record.
     */
    BookPo loadOne(QueryWrapper queryWrapper);

    /**
     * Throws the supplied exception if found no required record.
     */
    <E extends Throwable> BookPo loadOne(QueryWrapper queryWrapper, Supplier<? extends E> exceptionSupplier) throws E;

    long count(QueryWrapper queryWrapper);

    boolean exist(QueryWrapper queryWrapper);

    /**
     * Throws an exception if found no required record.
     */
    void assertExist(QueryWrapper queryWrapper);

    /**
     * Throws the supplied exception if found no required record.
     */
    <E extends Throwable> void assertExist(QueryWrapper queryWrapper, Supplier<? extends E> exceptionSupplier) throws E;

    boolean existOne(QueryWrapper queryWrapper);

    /**
     * Throws an exception if found no required record or found more than one record.
     */
    void assertExistOne(QueryWrapper queryWrapper);

    /**
     * Throws the supplied exception if found no required record or found more than one record.
     */
    <E extends Throwable> void assertExistOne(QueryWrapper queryWrapper, Supplier<? extends E> exceptionSupplier) throws E;

    long delete(@Nullable Condition condition);

    long update(BookColumnUpdate bookColumnUpdate, @Nullable Condition condition);
}
